using System.Linq;
using UnityEngine;

namespace Script.CreatureEditor
{
	public class Improvement : EditorAction
	{
		private enum Result
		{
			Create = 0,
			Destroy = 1
		}

		private Transform choosenBodyPart;

		private Transform choosenBodyPart2;

		private Renderer choosenRenderer;

		private Renderer choosenRenderer2;

		private GameObject choosenGameObject;

		private GameObject choosenGameObject2;

		private bool oko;

		private float skala;

		private Vector2 graniceBox;

		private Result result;

		private float posX;

		private Hand hand1;

		private Hand hand2;

		private bool hitTarget;

		private bool created;

		private bool eyeTag;

		public Improvement(EditorController editorController, Transform choosenBodyPart, Transform choosenBodyPart2, bool created)
			: base(editorController)
		{
			this.choosenBodyPart = choosenBodyPart;
			this.choosenBodyPart2 = choosenBodyPart2;
			this.created = (hitTarget = created);
			choosenRenderer = choosenBodyPart.GetComponentInChildren<Renderer>();
			choosenRenderer2 = choosenBodyPart2.GetComponentInChildren<Renderer>();
			choosenGameObject = choosenBodyPart.gameObject;
			choosenGameObject2 = choosenBodyPart2.gameObject;
			parents = editor.improvementInfo.parents;
			if (parents != null && created)
			{
				hand1 = editor.improvementContainer.GetChild(choosenBodyPart.GetSiblingIndex() - 2).GetComponentInChildren<Hand>();
				hand2 = editor.improvementContainer.GetChild(choosenBodyPart2.GetSiblingIndex() - 2).GetComponentInChildren<Hand>();
			}
			else if (parents == null)
			{
				hand1 = choosenBodyPart.GetComponentInChildren<Hand>();
				if ((bool)hand1)
				{
					hand2 = choosenBodyPart2.GetComponentInChildren<Hand>();
				}
			}
			oko = editor.improvementInfo.eye;
			skala = editor.body.localScale.x;
			posX = editor.body.position.x;
			eyeTag = choosenBodyPart.tag == "Eye";
			BoxCollider2D component = choosenBodyPart.GetComponent<BoxCollider2D>();
			float num = (component.size.y / 2f + component.offset.y) * skala;
			graniceBox = new Vector2(0f - num, num);
			component.enabled = false;
		}

		public override void End()
		{
		}

		public override void Update()
		{
			if (!Input.GetMouseButton(0))
			{
				bool flag = result == Result.Create && choosenRenderer.enabled && hitTarget;
				if (editor.SetImprovement(flag, created) && flag)
				{
					choosenBodyPart.SetParent(editor.improvementContainer);
					choosenBodyPart2.SetParent(editor.improvementContainer);
					if (parents != null && (bool)hand1)
					{
						choosenBodyPart.SetSiblingIndex(hand1.transform.parent.GetSiblingIndex() + 2);
						choosenBodyPart2.SetSiblingIndex(hand2.transform.parent.GetSiblingIndex() + 2);
						choosenGameObject.SetActive(hand1.transform.parent.gameObject.activeSelf);
						choosenGameObject2.SetActive(hand2.transform.parent.gameObject.activeSelf);
					}
					else
					{
						choosenGameObject2.SetActive(choosenRenderer2.enabled);
					}
					if (parents == null && (bool)hand1 && (bool)hand1.child)
					{
						hand2.child.gameObject.SetActive(choosenRenderer2.enabled);
					}
					choosenBodyPart.GetComponent<BoxCollider2D>().enabled = true;
					return;
				}
				Object.Destroy(choosenGameObject);
				Object.Destroy(choosenGameObject2);
				if (created)
				{
					editor.SellImprovement(choosenBodyPart.name);
				}
				if (parents == null && (bool)hand1 && (bool)hand1.child)
				{
					Object.Destroy(hand1.child.gameObject);
					Object.Destroy(hand2.child.gameObject);
					if (created)
					{
						editor.SellImprovement(hand1.child.name);
					}
				}
				return;
			}
			if (!HalfOfTheScreen())
			{
				if (result != Result.Destroy)
				{
					choosenGameObject.SetActive(false);
					choosenGameObject2.SetActive(false);
					result = Result.Destroy;
				}
				return;
			}
			result = Result.Create;
			Vector3 vector = WskazanyPunkt();
			if (editor.improvementInfo.oneAxis)
			{
				float num = posX - vector.x;
				if (num < 0f)
				{
					vector.x += num * 2f;
				}
			}
			if (parents != null)
			{
				Collider2D collider = Physics2D.OverlapPoint(vector);
				if ((bool)collider)
				{
					Hand componentInChildren = collider.GetComponentInChildren<Hand>();
					if ((bool)componentInChildren && componentInChildren != hand1 && !componentInChildren.child && parents.Any((string o) => o == collider.name))
					{
						if ((bool)hand1)
						{
							hand1.child = null;
							hand2.child = null;
						}
						componentInChildren.child = choosenBodyPart;
						choosenBodyPart.position = componentInChildren.parent.position;
						hand1 = componentInChildren;
						Transform copy = editor.GetCopy(collider.transform);
						componentInChildren = copy.GetComponentInChildren<Hand>();
						componentInChildren.child = choosenBodyPart2;
						choosenBodyPart2.position = componentInChildren.parent.position;
						hand2 = componentInChildren;
						hitTarget = true;
					}
				}
			}
			else
			{
				bool[] array = new bool[2];
				float num2 = 0.5f;
				if (oko)
				{
					num2 = 0.4f;
				}
				BoxCollider2D component = choosenBodyPart.GetComponent<BoxCollider2D>();
				Vector3 vector2 = choosenBodyPart.position + choosenBodyPart.right * component.offset.x * skala;
				Collider2D[] array2 = Physics2D.OverlapBoxAll(vector2, component.size * skala * num2, choosenBodyPart.eulerAngles.z);
				Collider2D[] array3 = array2;
				foreach (Collider2D collider2D in array3)
				{
					if (oko == editor.improvementsInfo[collider2D.name].eye)
					{
						if (collider2D.transform != choosenBodyPart2)
						{
							array = new bool[2] { true, true };
							break;
						}
						if (vector.x > posX && !oko)
						{
							array[0] = true;
						}
						else
						{
							array[1] = true;
						}
					}
				}
				if (vector.y > editor.bodyBounds.y)
				{
					choosenRenderer.enabled = false;
					choosenRenderer2.enabled = false;
					result = Result.Destroy;
					return;
				}
				choosenRenderer.enabled = !array[0];
				choosenRenderer2.enabled = !array[1];
			}
			if (hitTarget)
			{
				choosenGameObject.SetActive(true);
				choosenGameObject2.SetActive(true);
			}
			if (parents != null)
			{
				return;
			}
			RaycastHit raycastHit = (oko ? WskazaneMiejsceGora(vector) : WskazaneMiejsce(vector));
			Vector3 vector3 = default(Vector3);
			if (!raycastHit.transform)
			{
				if (!oko)
				{
					if (vector.y < 0f)
					{
						vector3.y = editor.bodyBounds.x;
					}
					else
					{
						vector3.y = editor.bodyBounds.y;
					}
					vector3.x = posX;
				}
				else
				{
					vector3 = choosenBodyPart.position;
				}
			}
			else
			{
				vector3 = raycastHit.point;
				hitTarget = true;
			}
			if (!oko)
			{
				vector3.z = 0f;
			}
			else if (eyeTag && vector3 != choosenBodyPart.position)
			{
				vector3.z -= 0.2f;
			}
			choosenBodyPart.position = vector3;
			choosenBodyPart2.position = new Vector3(vector3.x + (vector3.x - editor.body.position.x) * -2f, vector3.y, vector3.z);
			if ((bool)hand1 && (bool)hand1.child)
			{
				hand1.child.position = hand1.parent.position;
				hand2.child.position = hand2.parent.position;
			}
			if (editor.improvementInfo.rotationType == RotationType.Auto)
			{
				choosenBodyPart.rotation = Quaternion.identity;
				if (vector3.y <= editor.bodyBounds.x)
				{
					Obrot(choosenBodyPart, editor.body.GetChild(0).GetChild(8).position);
				}
				else
				{
					float y = choosenBodyPart.position.y;
					Vector2 vector4 = graniceBox + new Vector2(y, y);
					raycastHit = WskazaneMiejsce(new Vector2(vector.x, vector4.x));
					vector3.x = ((raycastHit.distance != 0f) ? raycastHit.distance : 1000f);
					vector3.y = WskazaneMiejsce(new Vector2(vector.x, vector4.y)).distance;
					float num3 = 57.29578f * Mathf.Atan((vector3.y - vector3.x) / (vector4.y - vector4.x));
					choosenBodyPart.rotation = Quaternion.Euler(0f, 0f, 0f - num3);
				}
				choosenBodyPart2.rotation = Quaternion.Euler(0f, 0f, 0f - choosenBodyPart.eulerAngles.z);
			}
			else if (editor.improvementInfo.rotationType == RotationType.Leg)
			{
				Vector2 bodyBounds = editor.bodyBounds;
				float num4 = vector3.y - bodyBounds.x;
				float num5 = Mathf.Lerp(-60f, 50f, 1f - num4 / (bodyBounds.y - bodyBounds.x));
				choosenBodyPart.rotation = Quaternion.Euler(0f, 0f, num5);
				choosenBodyPart2.rotation = Quaternion.Euler(0f, 0f, 0f - num5);
			}
		}

		protected RaycastHit WskazaneMiejsceGora(Vector3 punkt)
		{
			punkt.z = -10f;
			if (Mathf.Abs(punkt.x - posX) < 0.1f)
			{
				punkt.x = posX;
			}
			RaycastHit hitInfo;
			Physics.Raycast(punkt, Vector3.forward, out hitInfo, 100f);
			return hitInfo;
		}
	}
}
